package com.cyzy.service.impl;

import com.alipay.api.AlipayApiException;
import com.alipay.api.AlipayClient;
import com.alipay.api.DefaultAlipayClient;
import com.alipay.api.internal.util.AlipaySignature;
import com.alipay.api.request.AlipayTradeWapPayRequest;
import com.alipay.api.response.AlipayTradeWapPayResponse;
import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;
import com.baomidou.mybatisplus.core.conditions.update.UpdateWrapper;
import com.cyzy.config.AlipayConfig;
import com.cyzy.dto.AlipayPaymentRequest;
import com.cyzy.mapper.AlipayOrdersMapper;
import com.cyzy.mapper.PaymentMapper;
import com.cyzy.mapper.UserMapper;
import com.cyzy.pojo.AlipayOrders;
import com.cyzy.pojo.Payment;
import com.cyzy.service.AlipayService;
import jakarta.servlet.http.HttpServletRequest;
import lombok.extern.slf4j.Slf4j;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;

import java.math.BigDecimal;
import java.text.SimpleDateFormat;
import java.util.Date;
import java.util.HashMap;
import java.util.Iterator;
import java.util.Map;

/**
 * 支付宝支付服务实现类
 * @author LIGHT
 */
@Slf4j
@Service
public class AlipayServiceImpl implements AlipayService {

    @Autowired
    private AlipayConfig alipayConfig;

    @Autowired
    private PaymentMapper paymentMapper;

    @Autowired
    private AlipayOrdersMapper alipayOrdersMapper;

    @Autowired
    private UserMapper userMapper;

    @Override
    @Transactional
    public String createPayment(AlipayPaymentRequest paymentRequest) {
        try {
            // 1. 创建支付宝客户端
            AlipayClient alipayClient = new DefaultAlipayClient(
                    alipayConfig.getServerUrl(),
                    alipayConfig.getAppId(),
                    alipayConfig.getPrivateKey(),
                    alipayConfig.getFormat(),
                    alipayConfig.getCharset(),
                    alipayConfig.getPublicKey(),
                    alipayConfig.getSignType()
            );

            // 2. 创建支付请求
            AlipayTradeWapPayRequest request = new AlipayTradeWapPayRequest();

            // 3. 设置回调地址
            request.setNotifyUrl(alipayConfig.getNotifyUrl());
            request.setReturnUrl(alipayConfig.getReturnUrl());

            // 4. 计算金额（分转元）
            BigDecimal amount = BigDecimal.valueOf(paymentRequest.getAmount()).divide(BigDecimal.valueOf(100), 2, BigDecimal.ROUND_HALF_UP);

            // 5. 设置请求参数
            String bizContent = String.format(
                    "{\"out_trade_no\":\"%s\"," +
                            "\"total_amount\":\"%.2f\"," +
                            "\"subject\":\"%s\"," +
                            "\"product_code\":\"QUICK_WAP_WAY\"," +
                            "\"body\":\"%s\"}",
                    paymentRequest.getOrderNo(),
                    amount,
                    paymentRequest.getSubject(),
                    paymentRequest.getUserId()
            );
            request.setBizContent(bizContent);

            // 6. 插入payment表记录（状态为0-未支付）
            Payment payment = new Payment();
            payment.setOrderId(paymentRequest.getOrderId());
            payment.setUserId(paymentRequest.getUserId());
            payment.setPaymentMethod("余额充值");
            payment.setAmount(amount.doubleValue());
            payment.setStatus(0L); // 未支付
            payment.setCreatedAt(new java.sql.Timestamp(System.currentTimeMillis()));
            payment.setUpdatedAt(new java.sql.Timestamp(System.currentTimeMillis()));
            paymentMapper.insert(payment);

            // 7. 插入alipay_orders表记录（状态为2-待付款）
            AlipayOrders alipayOrder = new AlipayOrders();
            alipayOrder.setAlipayTraceNum(paymentRequest.getOrderNo());
            alipayOrder.setAlipayTotalAmount(amount.doubleValue());
            alipayOrder.setAlipaySubject(paymentRequest.getSubject());
            alipayOrder.setAlipayStatus(2L); // 待付款
            alipayOrdersMapper.insert(alipayOrder);

            // 8. 调用支付宝接口
//            AlipayTradeWapPayResponse response = alipayClient.pageExecute(request, "GET");
            AlipayTradeWapPayResponse response = alipayClient.pageExecute(request);
            String htmlForm = response.getBody();
            // 从HTML中提取URL
            String paymentUrl = extractUrlFromHtml(htmlForm);
            // 记录日志
            log.info("提取到的支付URL: {}", paymentUrl);
            return paymentUrl;

//            if (response.isSuccess()) {
//                log.info("支付宝支付订单创建成功，订单号：{}", paymentRequest.getOrderNo());
//                return response.getBody();
//            } else {
//                log.error("支付宝支付订单创建失败：{}", response.getSubMsg());
//                throw new RuntimeException("支付订单创建失败：" + response.getSubMsg());
//            }

        } catch (AlipayApiException e) {
            log.error("调用支付宝API异常：", e);
            throw new RuntimeException("支付接口调用失败", e);
        } catch (Exception e) {
            log.error("创建支付订单异常：", e);
            throw new RuntimeException("创建支付订单失败", e);
        }

    }

    private String extractUrlFromHtml(String htmlForm) {
        // 尝试提取form表单的action属性
        if (htmlForm.contains("form") && htmlForm.contains("action=")) {
            int startIndex = htmlForm.indexOf("action=\"") + 8;
            int endIndex = htmlForm.indexOf("\"", startIndex);
            if (startIndex > 8 && endIndex > startIndex) {
                return htmlForm.substring(startIndex, endIndex);
            }
        }

        // 尝试提取window.location.href
        if (htmlForm.contains("window.location.href")) {
            int startIndex = htmlForm.indexOf("window.location.href = '") + 24;
            int endIndex = htmlForm.indexOf("'", startIndex);
            if (startIndex > 24 && endIndex > startIndex) {
                return htmlForm.substring(startIndex, endIndex);
            }
        }

        // 如果都提取不到，则返回原始HTML
        return htmlForm;
    }

    @Override
    @Transactional
    public String handlePaymentNotify(HttpServletRequest request) {
        try {
            // 1. 获取支付宝POST过来的反馈信息
            Map<String, String> params = new HashMap<>();
            Map<String, String[]> requestParams = request.getParameterMap();
            
            for (Iterator<String> iter = requestParams.keySet().iterator(); iter.hasNext();) {
                String name = iter.next();
                String[] values = requestParams.get(name);
                String valueStr = "";
                for (int i = 0; i < values.length; i++) {
                    valueStr = (i == values.length - 1) ? valueStr + values[i] : valueStr + values[i] + ",";
                }
                params.put(name, valueStr);
            }

            log.info("支付宝回调参数：{}", params);

            // 2. 验证签名
            boolean signVerified = verifyNotify(params);
            if (!signVerified) {
                log.error("支付宝回调签名验证失败");
                return "failure";
            }

            // 3. 获取回调参数
            String outTradeNo = params.get("out_trade_no"); // 商户订单号
            String tradeNo = params.get("trade_no"); // 支付宝交易号
            String tradeStatus = params.get("trade_status"); // 交易状态
            String totalAmount = params.get("total_amount"); // 交易金额
            String body = params.get("body"); // 用户ID

            // 4. 判断交易状态
            if ("TRADE_SUCCESS".equals(tradeStatus) || "TRADE_FINISHED".equals(tradeStatus)) {
                
                // 5. 检查订单是否已经处理过
                QueryWrapper<AlipayOrders> orderQuery = new QueryWrapper<>();
                orderQuery.eq("alipay_trace_num", outTradeNo);
                AlipayOrders existingOrder = alipayOrdersMapper.selectOne(orderQuery);
                
                if (existingOrder != null && existingOrder.getAlipayStatus() == 1L) {
                    log.info("订单已处理过，订单号：{}", outTradeNo);
                    return "success";
                }

                // 6. 更新alipay_orders表
                UpdateWrapper<AlipayOrders> orderUpdate = new UpdateWrapper<>();
                orderUpdate.eq("alipay_trace_num", outTradeNo);
                orderUpdate.set("alipay_status", 1L); // 已付款
                orderUpdate.set("alipay_pay_time", new SimpleDateFormat("yyyy-MM-dd HH:mm:ss").format(new Date()));
                orderUpdate.set("alipay_trace_no", tradeNo);
                alipayOrdersMapper.update(null, orderUpdate);

                // 7. 更新payment表
                QueryWrapper<Payment> paymentQuery = new QueryWrapper<>();
                // 通过订单号关联查找payment记录
                QueryWrapper<AlipayOrders> findOrderQuery = new QueryWrapper<>();
                findOrderQuery.eq("alipay_trace_num", outTradeNo);
                AlipayOrders alipayOrder = alipayOrdersMapper.selectOne(findOrderQuery);
                
                if (alipayOrder != null) {
                    UpdateWrapper<Payment> paymentUpdate = new UpdateWrapper<>();
                    paymentUpdate.eq("amount", alipayOrder.getAlipayTotalAmount());
                    paymentUpdate.eq("status", 0L);
                    paymentUpdate.set("status", 1L); // 已支付
                    paymentUpdate.set("transaction_id", tradeNo);
                    paymentUpdate.set("pay_time", new java.sql.Timestamp(System.currentTimeMillis()));
                    paymentUpdate.set("updated_at", new java.sql.Timestamp(System.currentTimeMillis()));
                    paymentMapper.update(null, paymentUpdate);

                    // 8. 更新用户余额
                    if (body != null && !body.isEmpty()) {
                        Long userId = Long.parseLong(body);
                        BigDecimal amountToAdd = new BigDecimal(totalAmount);
                        int updateResult = userMapper.updateUserBalance(userId, amountToAdd);
                        
                        if (updateResult > 0) {
                            log.info("用户余额更新成功，用户ID：{}，充值金额：{}", userId, amountToAdd);
                        } else {
                            log.error("用户余额更新失败，用户ID：{}", userId);
                        }
                    }
                }

                log.info("支付成功处理完成，订单号：{}，支付宝交易号：{}", outTradeNo, tradeNo);
                return "success";
            } else {
                log.info("支付状态不是成功状态：{}", tradeStatus);
                return "success"; // 即使不是成功状态也返回success，避免支付宝重复通知
            }

        } catch (Exception e) {
            log.error("处理支付回调异常：", e);
            return "failure";
        }
    }

    @Override
    public boolean verifyNotify(Map<String, String> params) {
        try {
            return AlipaySignature.rsaCheckV1(params, alipayConfig.getPublicKey(), 
                    alipayConfig.getCharset(), alipayConfig.getSignType());
        } catch (AlipayApiException e) {
            log.error("验证支付宝签名异常：", e);
            return false;
        }
    }
} 